package com.loan.common.pay.hqpay;

import cn.hutool.http.ContentType;
import cn.hutool.http.Header;
import cn.hutool.http.HttpRequest;
import com.alibaba.fastjson.JSONObject;
import com.loan.common.enums.HttpMethod;
import com.loan.common.pay.oddpay.HttpClientUtil;
import com.loan.common.utils.DateUtils;
import com.loan.common.utils.HttpCommonClientUtils;
import com.loan.common.utils.HttpUtil;
import com.loan.common.utils.MD5;
import com.sun.org.apache.xpath.internal.operations.Bool;
import org.apache.commons.codec.digest.Md5Crypt;
import org.apache.commons.httpclient.HttpClient;

import java.io.IOException;
import java.security.KeyFactory;
import java.security.PublicKey;
import java.security.Signature;
import java.security.spec.X509EncodedKeySpec;
import java.util.*;

/**
 * hqpay支付工具类
 *
 * @author shiguang on 2022/9/16 14:17
 */
public class HQPayUtils {

    /**
     * 沙箱环境
     */
    private static final String API_URL = "https://merchant.hqpay.vn";

//    private static final String API_URL = "https://sandbox-merchant.hqpay.vn";

    private static final String VA_API_URL = "https://sandbox-va.hqpay.vn";

    private static final String LOGIN_URL = "/api/login";

    private static final String CREATE_VIRTUAL_CARD = "/api/request-new-card";

    private static final String PAY_URL = "/api/check-inquiry-and-transfer";

    private static final String RECHECK_URL = "/api/check-order";

//    private static final String PAY_URL = "/api/action-transfer";

    private static final String BANK_URL = "/api/list-banks";

    private static final String CREATE_NEW_VA = "/va/create";

    private static final String redis_key = "hqpay.";

    private static final String TOKEN = "Bearer eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiJ9.eyJhdWQiOiIyIiwianRpIjoiOGU5ZjBmYTH4tuZjwpUfVjtGpyrsDUdToQZmYW5ifhkNTQwNWE1ZDQ4MDRhNWM4MzY2YWQ5YmYzNDYzZWU4MDFhODJlZTH4tuZjwpUfVjtGpyrsDUdToQZmYW5ifhkMzgxLCJuYmYiOjE2Njc4OTk0MjMuMzY1Mzg1LCJleHAiOjE2OTk0MzU0MjMuMzU2NDA3LCJzdWIiOiIzOSIsInNjb3BlcyI6W119.YmpHcTLK8WBrBbe7nNZraFvGnJ9VEOxaw0zkDfyaCXJtzEz8lwqHdQ01OYuiNSVnntCayr1X6dURGxNl9brvZlsSLq98-WI3Ss-ygNKZb4dgw7pfOGG_fIqjD8lSke0paZzNhw68-ltvpcT7tVGNHCgfxOShhKlqoq247Aygc6HTVBerMTIUiv4Sk_1pywFaW1gfwMObIFAEXdB0qap2EwwU3wqaXE1Xs9HeCosdUVLhkGbe_-izZTHBAMwWHIjWwaZ2HLqZgnPffO_cbDwID9GA2iczDiFcnG_mDF64Ws6pGoJD1gwJ_MP-nU6tQ9FqEiTd3wHaHzJ7Bw9DpCgsTCAKOQVRHEeJLgmmXWrLXw36Z_7UA7b-EtREoYpQIqUn3Kjnn7zAr7qLecDFuJV3qHWF4DogUS58b1vdLcwvCZ4gz6n4dfkx6d62PLETWNqoe-QOKS4s-MO1SlWF_6royJZB9708niOSG3CzNEz0HyA9FpQD53MOe4swO0hzSnrHIX7HxZhHWKpvcti4pem3FbJVOi9A31v7TCs9rtv1AAnP_1MQg1Z9y5bs3BvN1VvKwGtbioL7iQ41rAa4b-KyDcvEGCq_OB3OTSj2ryhGTBriJBA_RrdQY8hzaEqJEJ1ptpLkxr2oaWagfDpZ-EnnYJcS_UiA0JBgzfkjoRGXIuU";

    private static final String PUBLIC_KEY = "MIGeMA0GCSqGSIb3DQEBAQUAA4GMADCBiAKBgH2oQH65he61Q3qTcVrvoNpovaPz5b/A2FgmZ+4V0UEqmJwEh6zkdrWacgAtp0ailL6L4HGE9Z8Lb4Bg1Q9rbo7jlf6rCS+qrKJHQJxf68X7jHjvw79o8JA7Ut4K6ng4CAxI1QyxBoFzs4wSBV3jIhcT0R1XtBkPK0M8tGaaAfXLAgMBAAE=";

    private static final String key = "MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDVUYFHPFb/cMqfRPDLIltKvE+yal6Yv+SKSpIevcyIKsEovqn2OzUuSOxEMl7pnxmW/JEG/4JBl0YtFdTTWafrwefvnQRsG4DcORTeu8RKDIWlkzbWGA/NnyGR6vDUsKTxKx03YUoMTOhgusWabH6BEX1aVdOUgYn7hJ4wiOg7gwIDAQAB";

    public static void main(String[] args) throws Exception {

//        String data1 = "{\"id\":\"77270\",\"amount\":1380000,\"tranDate\":\"2022-09-29 00:00:00\",\"tranId\":\"FT22272NKSXB\",\"cardId\":null,\"numberOfBeneficiary\":\"9704126093149402\",\"fee\":7000,\"description\":\"CHUYEN TIEN DEN SO TAI KHOAN 9704126093149402 - VI NGOC DUNG FT22272498220405-459872\",\"account\":\"109000941119\"}";
//        String data = "{\"id\":\"348\",\"amount\":100000,\"tranDate\":\"2021-08-13 00:00:00\",\"tranId\":\"FT21225STT09\",\"cardId\":null,\"numberOfBeneficiary\":\"NA\",\"fee\":1000,\"description\":\"bentest-TF00000276\",\"account\":\"106000852466\"}";
//        String data = "{\"tranId\":\"FT22272NKSXB\",\"amount\":1380000,\"numberOfBeneficiary\":\"9704126093149402\",\"fee\":7000,\"description\":\"CHUYEN TIEN DEN SO TAI KHOAN 9704126093149402 - VI NGOC DUNG FT22272498220405-459872\",\"tranDate\":\"2022-09-29 00:00:00\",\"id\":\"77270\",\"account\":\"109000941119\"}";
//        String signature = "WDtRUa3XMpdaOhs19nOdk8YU9ioHLy8c789TtbiXMKN2hAycKG5knwEYsgp0wWlyMoVuJr7uCmiV+1f01bawpFgvUZ66G8pUI/rSi2sZIof0uGwVAvwqU9dZPzVi2+gIApfJ6vDJCRwTsTsd2nCVBHNVle9vYEkIhjMdd6HWkjI=";
//        String signature = "VWUc3vJdIeNhE47cYtJCygPKyKLqDy3oHyWV/TRBQPHGN7RkbLhHsk2r9WjvEvmp8xDMfReIePeXJQZqCViBK1jLySTEdQFgjQR0ag2tLVi6p6gFzctk+qG7y7wBWIjego+te3Gb7CH2sfHKNaOFx1Per8rRx6xNBIbLk=";
//          String signature = "VWUc3vJdIeNhE47cYtJCygPKyKLqDy3oHyWV/TRBQPHGN7RkbLhHsk2r9WjvEvmp8xDMfReIePeXJQZqCViBK1jLySTEdQFgjQR0ag2tLVi6p6gFzctk+qG7y7wBWIjego+te3Gb7CH2sfHKNaOFx1Per8rRx6xNBIbLk=";
//        createVirtualCard();
//        pay();
//        byte[] bytes = Base64.decode(signature);
        //1667795960709
//        String token = login("861460170@qq.com", "12345678o");
//        verifySign(key,data1,signature);
//        System.out.println(signature.length());
//        System.out.println(signature1.length());
//        listBank(TOKEN);
//        HashMap<String, String> map = new HashMap<>();
//        map.put("data",data);
//        map.put("signature",signature);
//        String s = HttpClientUtil.httpGet("http://43.142.93.194:6060/api/hqpay/payment/callback", map);
//        System.out.println(s);
//        String newVa = createNewVa(String.valueOf(System.currentTimeMillis()), "test", "test", token);
//        System.out.println(JSONObject.parseObject(newVa));
//        String info = getInfo("HAV00130", token);
//        System.out.println(info);  FT212475L0F2  TFTL79qUJg
//        String pay = pay("HAV00153", "test", 10000, "99999", "202211080203", "test", TOKEN);
//        System.out.println(pay);
//        String result = transaction("HAV00153", DateUtils.getDate(),token);
//        System.out.println(result);
//        String result = queryPayOrder("202211070101", token);
//        System.out.println(result);
    }

    public static PublicKey getPublicKey(String key) {
        try {
            byte[] byteKey = Base64.getDecoder().decode(key);
            X509EncodedKeySpec x509EncodedKeySpec = new X509EncodedKeySpec(byteKey);
            KeyFactory keyFactory = KeyFactory.getInstance("RSA");
            return keyFactory.generatePublic(x509EncodedKeySpec);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }


    public static boolean verifySign(String key, String requestData, String signature) {
        boolean verifySignSuccess = false;
        try {
            PublicKey publicKey = getPublicKey(key);

            Signature verifySign = Signature.getInstance("sha256WithRSA");
            verifySign.initVerify(publicKey);
            verifySign.update(requestData.getBytes());

            verifySignSuccess = verifySign.verify(Base64.getDecoder().decode(signature));
            System.out.println("===验签结果：" + verifySignSuccess);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return verifySignSuccess;
    }


    /**
     * 登录
     *
     * @param email
     * @param password
     * @return
     */
    public static String login(String email, String password) {
        JSONObject json = new JSONObject();
        json.put("email", email);
        json.put("password", password);
//        String result = "";
        String result = HttpUtil.htPost(API_URL + LOGIN_URL, json.toString());
//        JSONObject jsonObject = JSONObject.parseObject(result);
//        String tokenType = jsonObject.getJSONObject("data").getString("token_type");
//        String accessToken = jsonObject.getJSONObject("data").getString("access_token");
//        System.out.println(tokenType + " " + accessToken);
//        return tokenType + " " + accessToken;
        return result;
    }

    /**
     * 创建虚拟卡
     *
     * @return
     */
    public static String createVirtualCard(String token) {
        String result = HttpUtil.sendGet(API_URL + CREATE_VIRTUAL_CARD, "", token);
        JSONObject jsonObject = JSONObject.parseObject(result);
        System.out.println("返回参数：" + jsonObject.toString());
        return result;
    }

    /**
     * 创建虚拟账户
     *
     * @param requestId
     * @param token
     * @return
     * @throws Exception
     */
    public static String createNewVa(String requestId,String userName,String companyName, String token) throws Exception {
        HashMap<String, Object> json = new HashMap<>();
        json.put("requestId", requestId);
        json.put("nameRule", "99");
        json.put("numberRule", "01");
        json.put("quantity", 1);
        json.put("description", companyName);
        json.put("returnAccount", true);
        List<Map<String, String>> list = new ArrayList<>();
        Map<String, String> map = new HashMap<>();
        map.put("vaNumber", "");
        map.put("vaName", userName);
        list.add(map);
        json.put("batch", list);
        return HttpCommonClientUtils.executeGethWithBody(VA_API_URL + CREATE_NEW_VA, json, token);
    }

    public static String getInfo(String number,String token) throws Exception {
        JSONObject json = new JSONObject();
        json.put("number", number);
        return HttpCommonClientUtils.executeGethWithBody(VA_API_URL + "/va/info", json, token);
    }

    public static String transaction(String number, String date, String token) throws Exception {
        JSONObject json = new JSONObject();
        json.put("number", number);
        json.put("date", date);
        return HttpCommonClientUtils.executeGethWithBody(VA_API_URL + "/va/transaction", json, token);
    }


    /**
     * 代付
     *
     * @return
     */
    public static String pay(String bankAccount, String name, Integer amount, String bankId, String orderNo, String remark, String token) {
        JSONObject json = new JSONObject();
        json.put("ftType", "ACC");
        json.put("numberOfBeneficiary", bankAccount);

        json.put("amount", amount);
        json.put("bankId", bankId);

        json.put("description", remark);
        json.put("order_number", orderNo);
        json.put("action", "cit");

        return HttpUtil.post(API_URL + PAY_URL, json.toString(), token);
    }

    /**
     * 代付
     *
     * @return
     */
//    public static String pay(String bankAccount, String name, Integer amount, String bankId, String orderNo, String remark, String token) {
//        JSONObject json = new JSONObject();
//        json.put("ftType", "ACC");
//        json.put("numberOfBeneficiary", bankAccount);
//
//        json.put("amount", amount);
//        json.put("bankId", "99999");
//
//        json.put("description", remark);
//        json.put("order_number", orderNo);
//        json.put("action", "t");
//        json.put("nameOfBeneficiary",name);
//
//        return HttpUtil.post(API_URL + PAY_URL, json.toString(), token);
//    }

    /**
     * 根据订单号查询订单
     * @return
     */
    public static String queryPayOrder(String requestId,String token){
        JSONObject json = new JSONObject();
        json.put("order_number", requestId);
        return HttpUtil.post(API_URL + RECHECK_URL, json.toString(), token);
    }


    public static String listBank(String token) {
        JSONObject json = new JSONObject();
        String result = HttpUtil.post(API_URL + BANK_URL, json.toString(), token);
        return result;
    }

    public static String payment(String data) {
        data = "{\"data\":\"{\\\"id\\\":\\\"348\\\",\\\"amount\\\":100000,\\\"tranDate\\\":\\\"2021-08-13 \n" +
                "00:00:00\\\",\\\"tranId\\\":\\\"FT21225STT09\\\",\\\"cardId\\\":null,\\\"numberOfBeneficiary\\\":\\\"NA\\\",\\\"f\n" +
                "ee\\\":1000,\\\"description\\\":\\\"bentestTF00000276\\\",\\\"account\\\":\\\"106000852466\\\"}\",\"signature\":\"WDtRUa3XMpdaOhs19nOdk8YU9ioHLy8c\n" +
                "789TtbiXMKN2hAycKG5knwEYsgp0wWlyMoVuJr7uCmiV+1f01bawpFgvUZ66G8pUI\\/rSi2sZIof0uGwVAvwqU9dZ\n" +
                "PzVi2+gIApfJ6vDJCRwTsTsd2nCVBHNVle9vYEkIhjMdd6HWkjI=\"}";
        JSONObject jsonObject = JSONObject.parseObject(data);
        JSONObject object = jsonObject.getJSONObject("data");
        String id = object.getString("id");
        String amount = object.getString("amount");
        String tranDate = object.getString("tranDate");
        String tranId = object.getString("tranId");
        String cardId = object.getString("cardId");
        String numberOfBeneficiary = object.getString("numberOfBeneficiary");
        String fee = object.getString("fee");
        String description = object.getString("description");
        String account = object.getString("account");
        String signature = object.getString("signature");
        return null;
    }

}
